import { getSession } from '@/lib/auth';
import { PAGE_SIZE } from '@/lib/constants';
import { db } from '@/lib/db';
import redis, { genMessageKey, genNewMessageNotOnlineKey } from '@/lib/redis';
import { result } from '@/lib/utils';
import { BizError, ErrorCode } from '../error';
import type { Message } from '../type/socket';

export const getMessages = async (data: {
  userId: string;
  shopUserId: string;
}) => {
  try {
    const key = genMessageKey(data);
    const messagesJSON = await redis.get(key);
    const messages = JSON.parse(messagesJSON || '[]') as Message[];
    return result(messages);
  } catch (error) {
    return result(error, '获取消息失败');
  }
};

export const listAllConversations = async () => {
  try {
    const session = await getSession();
    if (!session?.user)
      throw new BizError(ErrorCode.Unauthorized, '用户未登录');
    const pattern =
      session.user.role === 'user'
        ? genMessageKey({
            userId: session.user.id,
            shopUserId: '*',
          })
        : genMessageKey({
            userId: '*',
            shopUserId: session.user.id,
          });
    const keys = await redis.keys(pattern);
    const ids = keys.map((k) => {
      const arr = k.split(':');
      return session.user.role === 'user' ? arr[3] : arr[2];
    });
    const users = await db.query.user.findMany({
      where: (user, { inArray }) => inArray(user.id, ids),
      with: {
        shop: session.user.role === 'user' ? true : undefined,
      },
    });
    return result(users);
  } catch (error) {
    return result(error, '获取会话失败');
  }
};

export const shopListRecentlyConversations = async ({
  limit = PAGE_SIZE,
  shopUserId,
}: { limit?: number; shopUserId: string }) => {
  try {
    const pattern = genMessageKey({
      userId: '*',
      shopUserId,
    });
    const keys = await redis.keys(pattern);
    const keyItems = [];
    for (const key of keys) {
      keyItems.push({
        key,
        ttl: await redis.ttl(key),
      });
    }
    keyItems.sort((a, b) => b.ttl - a.ttl);
    const userIds = keyItems.slice(0, limit).map((item) => {
      const arr = item.key.split(':');
      return arr[2];
    });
    const users = [];
    for (const userId of userIds) {
      const userData = await db.query.user.findFirst({
        where: (user, { eq }) => eq(user.id, userId),
      });
      userData && users.push(userData);
    }
    return result(users);
  } catch (error) {
    return result(error, '获取会话失败');
  }
};

export const getNewMessagesNotify = async () => {
  try {
    const session = await getSession();
    if (!session?.user)
      throw new BizError(ErrorCode.Unauthorized, '用户未登录');
    const key = genNewMessageNotOnlineKey(session.user.id);
    const sendById = await redis.get(key);
    if (!sendById) return result();
    sendById && redis.del(key);
    const res = await db.query.user.findFirst({
      with:
        session.user.role === 'user'
          ? {
              shop: true,
            }
          : undefined,
      where: (user, { eq }) => eq(user.id, sendById),
    });
    return result({
      userId: sendById,
      name: session.user.role === 'user' ? (res as any)?.shop?.name : res?.name,
    });
  } catch (error) {
    return result(error, '获取新消息通知失败');
  }
};
